package com.mkh.st.common.utils;

import com.google.zxing.BarcodeFormat;
import com.google.zxing.EncodeHintType;
import com.google.zxing.MultiFormatWriter;
import com.google.zxing.WriterException;
import com.google.zxing.common.BitMatrix;
import com.google.zxing.qrcode.decoder.ErrorCorrectionLevel;
import lombok.extern.slf4j.Slf4j;
import sun.misc.BASE64Encoder;

import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.util.Hashtable;

/**
 * @author tsf
 * @date 2021/3/26 17:24
 * <p>
 * TODO
 */
@Slf4j
public class QRCodeUtil {

	private static final String CHARSET = "utf-8";

	// 二维码尺寸
	private static final int QRCODE_SIZE = 300;


	public static BufferedImage createImage(String content, Integer size) {
		Hashtable<EncodeHintType, Object> hints = new Hashtable<EncodeHintType, Object>();
		hints.put(EncodeHintType.ERROR_CORRECTION, ErrorCorrectionLevel.H);
		hints.put(EncodeHintType.CHARACTER_SET, CHARSET);
		hints.put(EncodeHintType.MARGIN, 0);
		size = (size == null ? QRCODE_SIZE : size);
		BitMatrix bitMatrix = null;
		try {
			bitMatrix = new MultiFormatWriter().encode(content, BarcodeFormat.QR_CODE, size, size,
					hints);
		} catch (WriterException e) {
			log.error("createImage error", e);
		}
		int width = bitMatrix.getWidth();
		int height = bitMatrix.getHeight();
		BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);

		for (int x = 0; x < width; x++) {
			for (int y = 0; y < height; y++) {
				image.setRGB(x, y, bitMatrix.get(x, y) ? 0xFF000000 : 0xFFFFFFFF);
			}
		}
		return image;
	}


	public static BufferedImage createImage(String content) {
		return createImage(content, QRCODE_SIZE);
	}

	public static String  createImageB64(String content) {
		return  toBase64(createImage(content, QRCODE_SIZE));
	}


	public static String  createImageB64(String content,Integer size) {
		return  toBase64(createImage(content, size));
	}



	/**
	 * BufferedImage 编码转换为 base64
	 *
	 * @param bufferedImage
	 * @return
	 */
	private static String toBase64(BufferedImage bufferedImage) {
		ByteArrayOutputStream baos = new ByteArrayOutputStream();//io流
		try {
			ImageIO.write(bufferedImage, "png", baos);//写入流中
		} catch (IOException e) {
			log.error("to b64 error:",e);
		}
		byte[] bytes = baos.toByteArray();//转换成字节
		BASE64Encoder encoder = new BASE64Encoder();
		String png_base64 = encoder.encodeBuffer(bytes).trim();//转换成base64串
		png_base64 = png_base64.replaceAll("\n", "").replaceAll("\r", "");//删除 \r\n
		return png_base64;
	}
}
